package com.ease.concurrent.volat;

/**
 * volatile典型应用场景：
 * 只有一个修改者，多个使用者，要求保证可见性的场景
 * 1、状态标识，如示例VisibilityDemo中的介绍标识。
 * 2、数据定期发布，多个获取者。
 *
 *
 * 懒汉式单例模式
 *
 * (1)处第一次检查，确保的是逻辑上正确；synchronized关键字保证了100个线程共享同一把锁。
 * 只有一个线程抢到锁进行实例创建，另外99个线程在外面(2)处等待。
 * 当该线程完成实例创建，在(4)处释放锁，这时候在外面等待创建实例的另外99个线程一股涌进来了。
 * 这时由于instance变量的volatile关键字保证了可见性，(3)处进行第二次检查。发现实例不为空，
 * 立即返回。至此，单例功能完成使命。
 *
 * @author: chenhs
 * @date: Created in 6:36 2019/11/7
 **/
public class Singleton {

    /** 此处的volatile修饰满足的是高并发、高性能需要*/
    private static volatile Singleton instance;

    private Singleton(){}

    /** 满足单例的正确性由同步关键字synchronize和双重检测完成的*/
    public static Singleton getInstance() {
        //第一次检查(1)
        if (instance == null) {
            //创建实例(2)
            synchronized (Singleton.class){
                //第二次检查(3)
                if (instance == null) {
                    instance = new Singleton();
                }//(4)
            }
        }

        return instance;
    }

}
